/** @odoo-module **/

import {ControlPanel} from "@web/search/control_panel/control_panel";

import {registry} from "@web/core/registry";
import {useService} from "@web/core/utils/hooks";
import {Component, onWillStart, useState} from "@odoo/owl";

export class SMaterialRequirementsAnalysisComponent extends Component {
    setup() {
        this.orm = useService("orm");

        this.saleLines = useState([]);
        this.materialConsumptionList = useState([]);
        onWillStart(async () => {
            await this.getSaleOrderInfo();
            await this.computeMaterialConsumptionList();
        });


    }

    addDataToSaleLines(data) {
        this.saleLines.unshift(...data);
    }

    async getSaleOrderInfo() {
        const data = await this.orm.call(
            "s.material.requirements.analysis.report",
            "get_data"
        );
        const saleLines = data['sale_line_vals_list']
        this.addDataToSaleLines(saleLines)
        this.bomData = data['bom_vals']
        this.materialProductData = data['material_product_vals']
    }

    async computeMaterialConsumptionList() {
        const materialConsumption = {}; // 存储每个产品的总消耗量
        this.materialConsumptionList.length = 0;

        // 遍历销售订单信息
        this.saleLines.forEach(line => {
            const bom = this.bomData[line.product_id]; // 获取当前产品对应的BOM数据

            if (!bom) {
                console.warn(`No BOM data found for product ID: ${line.product_id}`);
                return; // 如果没有BOM数据，跳过该行
            }

            // 遍历 BOM 数据
            for (const [product, qty] of Object.entries(bom)) {
                const productInfo = this.materialProductData[product] || {};
                const productCr = productInfo['product_cr'];

                if (!this.materialProductData[product]) {
                    console.warn(`No material product data found for product: ${product}`);
                    continue; // 如果没有对应的物料数据，跳过该产品
                }

                // 根据 productCr 的值选择不同的计算方法
                let consumptionQty;
                if (productCr) {
                    // 如果 productCr 为真，使用第一种计算方式
                    consumptionQty = (line.expect_planned_pnl_qty / line.value_sheet) * qty;
                } else {
                    // 否则使用第二种计算方式
                    consumptionQty = parseFloat((line.expect_planned_qty * qty).toFixed(3));
                }

                // 判断 product 是否已经在 materialConsumption 中
                if (materialConsumption[product]) {
                    // 如果存在，叠加数量
                    materialConsumption[product] += consumptionQty;
                } else {
                    // 如果不存在，初始化数量
                    materialConsumption[product] = consumptionQty;
                }
            }
        });

        // 将结果存储到 materialConsumptionTotal 中
        Object.entries(materialConsumption).forEach(([product, totalQty]) => {
            const productInfo = this.materialProductData[product] || {};
            const product_stock_qty = productInfo['product_stock_qty'];
            let diff = 0
            if (product_stock_qty < totalQty) {
                diff = parseFloat((totalQty - product_stock_qty).toFixed(3))
            }

            const other = { product, diff, totalQty}
            // 构造最终结果对象
            this.materialConsumptionList.unshift({...productInfo, ...other});
        });

    }

    onChangeSale(saleId, scrapRate) {

        // 查找目标记录
        const targetItem = this.saleLines.find(item => item.id === saleId);
        if (!targetItem) {
            return;
        }

        // 提取必要字段
        const {value_pnl, value_sheet, product_qty} = targetItem;

        // 计算新的值
        const adjustedScrapRate = 1 + (scrapRate / 100);
        const baseValue = value_sheet * value_pnl;
        const expectPlannedQty = Math.ceil((product_qty * adjustedScrapRate) / baseValue) * baseValue;
        const expectPlannedPnlQty = expectPlannedQty / value_sheet;

        // 更新目标记录
        targetItem.expect_planned_qty = expectPlannedQty;
        targetItem.expect_planned_pnl_qty = expectPlannedPnlQty;
        this.computeMaterialConsumptionList()
    }

    deleteSaleLine(saleId) {
        this.saleLines = this.saleLines.filter(item => item.id !== saleId);
        this.computeMaterialConsumptionList()
    }
}

SMaterialRequirementsAnalysisComponent.template = "sb_plan.MaterialRequirementsAnalysisComponent";
SMaterialRequirementsAnalysisComponent.components = {
    ControlPanel,
};
registry.category("actions").add("s_material_requirements_analysis", SMaterialRequirementsAnalysisComponent);